package com.practice.service.impl;

import com.practice.service.MinioService;
import io.minio.*;
import io.minio.http.Method;
import io.minio.messages.Item;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.http.HttpMethod;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;

@Service
public class MinioServiceImpl implements MinioService {

    private final MinioClient minioClient;
    private final String bucketName;

    public MinioServiceImpl(MinioClient minioClient, @Value("${minio.bucket-name}") String bucketName) {
        this.minioClient = minioClient;
        this.bucketName = bucketName;
    }

    /**
     * 上传文件到 MinIO并返回文件的 URL
     * @param file 1
     * @return 1
     * @throws Exception 1
     */
    public String uploadFile(MultipartFile file) throws Exception {
        // 检查存储桶是否存在，如果不存在则创建
        if (!minioClient.bucketExists(BucketExistsArgs.builder().bucket(bucketName).build())) {
            minioClient.makeBucket(MakeBucketArgs.builder().bucket(bucketName).build());
        }

        // 获取文件输入流
        try (InputStream inputStream = file.getInputStream()) {
            // 上传文件到指定存储桶
            minioClient.putObject(PutObjectArgs.builder()
                    .bucket(bucketName)
                    .object(file.getOriginalFilename())  // 文件名
                    .stream(inputStream, file.getSize(), -1) // 文件输入流和大小
                    .contentType(file.getContentType())  // 文件内容类型
                    .build());
        }

        // 返回文件的预签名 URL
        return getFileUrl(file.getOriginalFilename());
    }

    /**
     * 获取文件的 URL
     * @param fileName 1
     * @return 1
     * @throws Exception 1
     */
    public String getFileUrl(String fileName) throws Exception {
        // 获取文件的预签名 URL，默认有效期为 7 天
        GetPresignedObjectUrlArgs getPresignedObjectUrlArgs = GetPresignedObjectUrlArgs.builder()
                .bucket(bucketName)
                .object(fileName)
                .method(Method.GET)  // 设置 HTTP 方法为 GET
                .expiry(7 * 24 * 60 * 60)  // 设置 URL 有效期为 7 天
                .build();

        return minioClient.getPresignedObjectUrl(getPresignedObjectUrlArgs);
    }

    /**
     * 列出存储桶中的所有文件
     * @return 1
     * @throws Exception 1
     */
    public List<Item> listFiles() throws Exception {
        List<Item> items = new ArrayList<>();
        // 使用 ListObjectsArgs 来列出对象
        Iterable<Result<Item>> results = minioClient.listObjects(ListObjectsArgs.builder().bucket(bucketName).build());

        for (Result<Item> result : results) {
            // 获取每个文件对象
            items.add(result.get());
        }
        return items;
    }
}
